import themes from './themes'

export default class {
  constructor(config?: ThemeConfig) {
    if (config) this.themeConfig = Object.assign(this.themeConfig, config)
  }

  private themeConfig: ThemeConfig = { code: 'code' }
  private theme: Theme = null
  private themes: Theme[] = themes

  // 获取当前主题
  public getTheme() {
    return this.theme
  }

  // 设置当前主题
  public setTheme(theme: Theme) {
    if (theme[this.themeConfig.code] === 'auto') {
      const darkTheme: Theme = this.themes.find(theme => {
        return theme[this.themeConfig.code] === 'dark'
      })

      const lightTheme: Theme = this.themes.find(theme => {
        return theme[this.themeConfig.code] === 'light'
      })

      const autoTheme: Theme = this.themes.find(theme => {
        return theme[this.themeConfig.code] === 'auto'
      })

      const isDarkMode: boolean = window.matchMedia && window.matchMedia('(prefers-color-scheme: dark)').matches

      theme = Object.assign(theme, isDarkMode ? darkTheme : lightTheme, autoTheme)
    }

    this.theme = theme

    localStorage && localStorage.setItem('theme', JSON.stringify(theme))

    const rootElement: HTMLElement = document.querySelector(':root')

    for (const k in this.theme) {
      rootElement.style.setProperty(k, this.theme[k])
    }

    return this.theme
  }

  // 设置全部主题
  public setThemes(themes: Theme[]) {
    this.themes = themes

    return this.themes
  }

  // 添加主题
  public addTheme(theme: Theme) {
    const existTheme: Theme = this.themes.find((item: Theme) => {
      return item[this.themeConfig.code] === theme[this.themeConfig.code]
    })

    if (existTheme) return false

    return this.themes.push(theme)
  }

  // 删除主题
  public removeTheme(code: string) {
    const index: number = this.themes.findIndex((theme: Theme) => {
      return theme[this.themeConfig.code] === code
    })

    if (index !== -1) return this.themes.splice(index, 1)

    return false
  }

  install() {
    if (localStorage && localStorage.getItem('theme')) this.theme = JSON.parse(localStorage.getItem('theme'))

    this.setTheme(this.theme)

    const mediaLight = window.matchMedia('(prefers-color-scheme: light)')
    const mediaDark = window.matchMedia('(prefers-color-scheme: dark)')

    mediaLight.addListener((e) => {
      if (e.matches) this.setTheme(this.theme)
    })

    mediaDark.addListener((e) => {
      if (e.matches) this.setTheme(this.theme)
    })
  }
}